﻿using System;
using System.Collections.Generic;

using System.Text;
using System.Windows.Forms;
using EnvDTE;
using EnvDTE80;
using Microsoft.VisualStudio.CommandBars;



namespace DoxygenBrowserAddin
{
  public class VSAddinHelper
  {
    private DTE2 _applicationObject;
    private AddIn _addInInstance;


    public VSAddinHelper(DTE2 applicationObject, AddIn addInInstance)
    {
      _applicationObject = applicationObject;
      _addInInstance = addInInstance;
    }

    /// <summary>
    /// Add a command bar to the VS2005 interface.
    /// </summary>
    /// <param name="name">The name of the command bar</param>
    /// <param name="commandBarParent">The command bar parent.</param>
    /// <param name="iPosition">The i position.</param>
    /// <returns></returns>
    public CommandBar AddCommandBar(string name, CommandBar commandBarParent, int iPosition)
    {
      Commands2 commands = (Commands2)_applicationObject.Commands;

      CommandBar bar = null;
        // Create the new CommandBar
        bar =
          (CommandBar)commands.AddCommandBar(name, vsCommandBarType.vsCommandBarTypeMenu, commandBarParent, iPosition);
      return bar;
    }

    /// <summary>
    /// Add a menu to the VS2005 interface.
    /// </summary>
    /// <param name="name">The name of the menu</param>
    /// <returns></returns>
    public CommandBar AddCommandMenu(string name, CommandBars commandBars)
    {
      // Get the command bars collection
      CommandBars cmdBars =
          ((Microsoft.VisualStudio.CommandBars.CommandBars)
          commandBars);
      CommandBar menu = null;

      try
      {
        try
        {
          // Create the new CommandBar
          menu = cmdBars.Add(name, MsoBarPosition.msoBarPopup,
                          false, false);
        }
        catch (ArgumentException)
        {
          // Try to find an existing CommandBar
          menu = cmdBars[name];
        }
      }
      catch
      {
      }

      return menu;
    }

    /// <summary>
    /// Add a command to a popup menu in VS2005.
    /// </summary>
    /// <param name="popup">The popup menu to add the command to.</param>
    /// <param name="name">The name of the new command.</param>
    /// <param name="label">The text label of the command.</param>
    /// <param name="ttip">The tooltip for the command.</param>
    /// <param name="iconIdx">The icon index, which should match the resource ID 
    /// in the add-ins resource assembly.</param>
    public void AddPopupCommand(
        CommandBarPopup popup, string name, string label,
    string ttip, int iconIdx)
    {
      // Do not try to add commands to a null menu
      if (popup == null)
        return;

      // Get commands collection
      Commands2 commands = (Commands2)_applicationObject.Commands;
      object[] contextGUIDS = new object[] { };

      try
      {
        // Add command
        Command command = commands.AddNamedCommand2(_addInInstance,
            name, label, ttip, false, iconIdx, ref contextGUIDS,
            (int)vsCommandStatus.vsCommandStatusSupported +
            (int)vsCommandStatus.vsCommandStatusEnabled,
            (int)vsCommandStyle.vsCommandStylePictAndText,
            vsCommandControlType.vsCommandControlTypeButton);
        if ((command != null) && (popup != null))
        {
          command.AddControl(popup.CommandBar, 1);
        }
      }
      catch (ArgumentException)
      {
        // Command already exists, so ignore
      }
    }

    /// <summary>
    /// Add a command to a toolbar in VS2005.
    /// </summary>
    /// <param name="bar">The bar to add the command to.</param>
    /// <param name="strName">Name of the STR.</param>
    /// <param name="strButtonText">The STR button text.</param>
    /// <param name="ttip">The tooltip for the command.</param>
    /// <param name="iconIdx">The icon index, which should match the resource ID in the add-ins resource assembly.</param>
    /// <returns></returns>
    public Command AddToolbarCommand(CommandBar bar, string strName, string strButtonText,
    string ttip, int iconIdx)
    {
      Command command = null;
      // Do not try to add commands to a null bar
      if (bar == null)
        return null;

      // Get commands collection
      Commands2 commands = (Commands2)_applicationObject.Commands;
      object[] contextGUIDS = new object[] { };

      try
      {
        command = Find(commands, strName);
        if (command == null)
        {
          // Add command
          command = commands.AddNamedCommand2(_addInInstance, strName,
                                              strButtonText, ttip, true, iconIdx, ref contextGUIDS,
                                              (int)vsCommandStatus.vsCommandStatusSupported +
                                              (int)vsCommandStatus.vsCommandStatusEnabled,
                                              (int)vsCommandStyle.vsCommandStylePict,
                                              vsCommandControlType.vsCommandControlTypeButton);
        }
        if (command != null && bar != null)
        {
          command.AddControl(bar, 1);
        }

      }
      catch (ArgumentException)
      {
        // Command already exists, so ignore
      }

      return command;
    }

    public void Binding(Command command, string hotkey)
      {
      command.Bindings = hotkey;
    }

    private Command Find(Commands2 commands, string name)
    {
      Command command = null;
      try
      {
        command = commands.Item(_addInInstance.ProgID + "." + name, -1);
      }
      catch(ArgumentException)
      {
        // isnt' found
        command = null;
      }
      return command;
    }

  }
}
